package com.acme.bankapp.domain.bank;

/**
 * Class representing client
 */
public class Client {

    /**
     * Gender Enum
     */
    public static enum Gender{
        MALE("Mr."), FEMALE("Ms.");

        private String namePrefix;

        Gender(String namePrefix){
            this.namePrefix = namePrefix;
        }

        public String getNamePrefix(){
            return namePrefix;
        }
    }


    private Account account;

    private String name;

    private Gender gender;


    /**
     * Constructs client
     */
    public Client(){
    }

    /**
     * Constructs client with specified name
     * @param name Name
     */
    public Client(String name){
        this(name,Gender.MALE);
    }

    /**
     * Constructs client with specified name and gender
     * @param name Name
     * @param gender Gender
     */
    public Client(String name, Gender gender){
        this();
        this.name = name;
        this.gender = gender;
    }

    /**
     * Get client name
     * @return name
     */
    public String getName() {
        return name;
    }

    /**
     * Set client name
     * @param name Name to set
     */
    public void setName(String name) {
        this.name = name;
    }

    /**
     * Get client gender
     * @return Client gender
     */
    public Gender getGender() {
        return gender;
    }

    /**
     * Set client gender
     * @param gender Sets client gender
     */
    public void setGender(Gender gender) {
        this.gender = gender;
    }

    /**
     * Returns user account
     * @return User's account (or null if not present)
     */
    public Account getAccount() {
        return account;
    }

    /**
     * Sets user account. To assure integrity use com.acme.bankapp.service.bank.BankService.associateClientWithAccount
     * @see com.acme.bankapp.service.bank.BankService
     * @param account User account to set
     */
    public void setAccount(Account account) {
        this.account = account;
    }

    /**
     * Get client salutation string
     * @return salutation
     */
    public String getClientSalutation(){
        return gender.getNamePrefix() + " " + name;
    }

    @Override
    public boolean equals(Object o) {
        if (this == o) return true;
        if (o == null || getClass() != o.getClass()) return false;

        Client client = (Client) o;

        if (gender != client.gender) return false;
        if (name != null ? !name.equals(client.name) : client.name != null) return false;

        return true;
    }

    @Override
    public int hashCode() {
        int result = name != null ? name.hashCode() : 0;
        result = 31 * result + (gender != null ? gender.hashCode() : 0);
        return result;
    }

    @Override
    public String toString() {
        StringBuilder builder = new StringBuilder();
        builder
            .append(" Name: ")
            .append(name)
            .append(" Gender: ")
            .append(gender.toString())
            .append(" Account balance: ")
            .append(account != null ? account.getDecimalBalance() : "No account");
        return builder.toString();
    }
}
